/*
*Copyright 2021-2023 NERCIS
*
*Licensed under the Apache License, Version 2.0 (the "License");
*you may not use this file except in compliance with the License.
*You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
*Unless required by applicable law or agreed to in writing, software
*distributed under the License is distributed on an "AS IS" BASIS,
*WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
*See the License for the specific language governing permissions and
*limitations under the License.
*/

package cn.ac.nercis.pes.community.component.controls;

import cn.ac.nercis.pes.common.constant.common.BaseConstants;
import javafx.beans.property.BooleanProperty;
import javafx.beans.property.ObjectProperty;
import javafx.beans.property.SimpleBooleanProperty;
import javafx.beans.property.SimpleObjectProperty;
import javafx.scene.control.Label;
import javafx.scene.control.Toggle;
import javafx.scene.control.ToggleGroup;
import javafx.scene.control.Tooltip;
import javafx.scene.input.MouseEvent;
import javafx.scene.layout.VBox;
import org.apache.commons.lang3.StringUtils;

import java.util.Objects;
import java.util.stream.Stream;

/**
 * 预期结果选择自定义控件
 *
 * @author zpy
 * @version 1.0.0
 */
public class ExpectedResultSelectControl extends VBox implements Toggle {
    private static final String DEFAULT_STYLE = "choose-container";

    private final String content;

    private ObjectProperty<ToggleGroup> toggleGroup;
    private BooleanProperty selected;

    public ExpectedResultSelectControl(String content) {
        this(content, DEFAULT_STYLE);
    }

    public ExpectedResultSelectControl(String content, String styleCss) {
        this.content = content;
        this.getStyleClass().add(styleCss);
        this.initControl();
    }

    @Override
    public ToggleGroup getToggleGroup() {
        return Objects.isNull(toggleGroup) ? null : toggleGroup.get();
    }

    @Override
    public void setToggleGroup(ToggleGroup toggleGroup) {
        toggleGroupProperty().set(toggleGroup);
    }

    @Override
    public ObjectProperty<ToggleGroup> toggleGroupProperty() {
        if (Objects.isNull(toggleGroup)) {
            toggleGroup = new SimpleObjectProperty<>();
        }
        return toggleGroup;
    }

    @Override
    public boolean isSelected() {
        return selectedProperty().get();
    }

    public void setSelected(boolean selected) {
        this.selected.set(selected);
        this.getStyleClass().removeAll("choose-container", "choose-container-selected");
        if (selected) {
            this.getStyleClass().add("choose-container-selected");
        } else {
            this.getStyleClass().add("choose-container");
        }
    }

    @Override
    public BooleanProperty selectedProperty() {
        if (Objects.isNull(selected)) {
            selected = new SimpleBooleanProperty(false);
        }
        return selected;
    }

    public String getContent() {
        return content;
    }

    private void initControl() {
        if (StringUtils.isBlank(content)) {
            return;
        }
        Stream.of(content.split(BaseConstants.REGEX_WRAP_TEXT_SPLIT))
                .filter(StringUtils::isNotBlank)
                .forEach(item -> {
                    Label label = new Label(item);
                    label.setWrapText(true);
                    label.setTooltip(new Tooltip(item));
                    this.getChildren().add(label);
                });
        this.setOnMouseClicked(this::onMouseClick);
    }

    private void onMouseClick(MouseEvent me) {
        if (Objects.isNull(toggleGroup)) {
            this.setSelected(!this.selected.get());
            return;
        }
        toggleGroup.get().getToggles()
                .stream()
                .filter(t -> t instanceof ExpectedResultSelectControl)
                .map(t -> (ExpectedResultSelectControl) t)
                .forEach(t -> t.setSelected(Objects.equals(t, this)));
    }
}